/*
 * To change this template, choose Tools | Templates
 * and open the template in the editor.
 */

package server.negocio;



import com.mysql.jdbc.exceptions.jdbc4.MySQLIntegrityConstraintViolationException;
import java.util.Date;
import server.dominio.Hora;
import server.dominio.ISesion;
import server.dominio.Sesion;
import server.dominio.Usuario;
import java.sql.SQLException;
import java.util.ArrayList;
import java.util.Vector;
import server.dominio.Beneficiario;
import server.dominio.Cita;
import server.dominio.Medico;

import server.excepciones.BeneficiarioInexistenteException;
import server.excepciones.BeneficiarioNoExistenteException;
import server.excepciones.BeneficiarioYaExistenteException;
import server.excepciones.CitaNoValidaException;
import server.excepciones.CitaYaExistenteException;
import server.excepciones.FechaNoValidaException;
import server.excepciones.MedicoInexistenteException;
import server.excepciones.MedicoNoExistenteException;
import server.excepciones.MedicoYaExistenteException;
import server.persistencia.DAOFactory;
import server.persistencia.DAOUsuario;
import server.excepciones.UsuarioIncorrectoException;
import server.excepciones.UsuarioNoExistenteException;

import server.excepciones.UsuarioYaExistenteException;
import server.persistencia.DAOBeneficiario;
import server.persistencia.DAOCentro;
import server.persistencia.DAOCita;
import server.persistencia.DAOHora;
import server.persistencia.DAOMedico;
import server.persistencia.DAOMedicoMySQL;

/**
 *
 * @author tpaxle
 */
public class Fachada_Servidor {
   // private
    private DAOFactory factoriadaos;

    public Fachada_Servidor(){
        factoriadaos= DAOFactory.getFactory();
    }


    /*Metodos Login, obtener login, y comprobar login correcto*/
    public ISesion getlogin(String login, String password) throws SQLException, UsuarioIncorrectoException{
        
        ISesion devuelta = null;
        DAOUsuario daou = factoriadaos.crearDAOUsuario();
        ArrayList<Object> usuario =  daou.select("SELECT * FROM usuario WHERE login='"+login+"' and pass= '" + password+"'");
        daou.cerrarDAO();
        if(usuario.size()==0){
            //lanzar Usuario no encontrado exception
            throw new UsuarioIncorrectoException("Usuario: "+ login + ". Password: " + password +", no se encuentra en la base de datos");
        }

        Usuario aux= (Usuario)usuario.get(0);

        devuelta= new Sesion(-1, aux.getRol());

//        return devuelta;
        return devuelta;
    }
    /*************************************************************/
    /*************************************************************/


    /*Obtener datos de interfaz
     * getBeneficiario: obtiene el beneficiario con dni ='dni'
     * getBeneficiarionss: obtiene el beneficiario con nss ='nss'
     * getMedico: obtiene el medico con dni ='dni'
     */
    public Beneficiario getBeneficiario(String dni) throws SQLException, BeneficiarioInexistenteException{
        Beneficiario bene= null;
        DAOBeneficiario daoBene= factoriadaos.crearDAOBeneficiario();
        ArrayList<Object> beneficiario = daoBene.select("SELECT * FROM Beneficiario WHERE Nif= '"+dni+"'");
        daoBene.cerrarDAO();
        if(beneficiario.size()==0)
            throw new BeneficiarioInexistenteException(dni);
        else{
            bene= (Beneficiario)beneficiario.get(0);
        }

        return bene;
    }
    public Beneficiario getBeneficiarionss(String nss) throws SQLException, BeneficiarioInexistenteException {
        Beneficiario bene= null;
        DAOBeneficiario daoBene= factoriadaos.crearDAOBeneficiario();
        bene = (Beneficiario) daoBene.find("SELECT * FROM Beneficiario WHERE nss= '"+nss+"'");
        daoBene.cerrarDAO();
        if(bene== null)
            throw new BeneficiarioInexistenteException("El beneficiario con nss "+ nss+", no existe");

        return bene;
    }
    public Medico getMedico(String dni) throws SQLException, MedicoInexistenteException{
        Medico medico= null;
        DAOMedico daoMe= factoriadaos.crearDAOMedico();
        medico= (Medico) daoMe.find("SELECT * FROM Medico, Usuario Where Medico.idUsuario_fk= Usuario.idUsuario_pk and Nif= '"+dni+"'");
        daoMe.cerrarDAO();
        if(medico== null)
            throw new MedicoInexistenteException("El medico con: "+dni+ ", no existe");
        return medico;
    }
    /***************************************************************/
    /***************************************************************/
    /***************************************************************/



    /*Insercion de datos en la base de datos
     * Beneficiario, medico, husuario u horas
     * 
     */
    public void nuevobeneficiario(Beneficiario beneficiario) throws SQLException, BeneficiarioYaExistenteException{
        DAOBeneficiario daoBeneficiario= factoriadaos.crearDAOBeneficiario();
        try{
            daoBeneficiario.insert(beneficiario);
        } catch (com.mysql.jdbc.exceptions.jdbc4.MySQLIntegrityConstraintViolationException ex) {
            //Ya hay un usuario con el mismo nif o el mismo login
            throw new BeneficiarioYaExistenteException(ex.toString());
        }finally{
            daoBeneficiario.cerrarDAO();
        }
    }
    public void nuevomedico(Medico medico) throws SQLException, MedicoYaExistenteException {
        DAOMedico daoMedico= factoriadaos.crearDAOMedico();

        try {
            daoMedico.insert(medico);
        } catch (MySQLIntegrityConstraintViolationException ex) {
            //Ya hay un usuario con el mismo nif o el mismo login
            throw new MedicoYaExistenteException(ex.toString());
        }finally{
            daoMedico.cerrarDAO();
        }
    }
    public void nuevousuario(Usuario usuario) throws UsuarioYaExistenteException, SQLException{
        DAOUsuario daoUsuario = factoriadaos.crearDAOUsuario();
        try {
            daoUsuario.insert(usuario);
        } catch (MySQLIntegrityConstraintViolationException ex) {
            throw new UsuarioYaExistenteException("El usario:\n "+ usuario+"\nExiste:");
        } finally{
            daoUsuario.cerrarDAO();            
        }

    }
    public int insertarhora(Hora hora_insert) throws SQLException {
        DAOHora daoHora= factoriadaos.crearDAOHora();
        int resultado = 0;
        resultado= daoHora.insert(hora_insert);
        daoHora.cerrarDAO();
        return resultado;

    }



  //true significa que existe medico perdido
    public Medico comprobarmedicoperdido(Medico medico_aux) throws SQLException {
        DAOMedico daom= factoriadaos.crearDAOMedico();
        Medico medico= (Medico) daom.find("SELECT * FROM Medico, Usuario WHERE idUsuario_fk= idUsuario_pk and idUsuario_pk= "+ medico_aux.getIdUsuario_pk());
        daom.cerrarDAO();
        return medico;
    }
 



    /**Modificacion de datos**/
    public void actualizar(Beneficiario beneficiario) throws SQLException, BeneficiarioYaExistenteException, BeneficiarioNoExistenteException  {
        DAOBeneficiario daobene= null;
        try{
            daobene= factoriadaos.crearDAOBeneficiario();
            int resul= daobene.update(beneficiario);

        } catch (MySQLIntegrityConstraintViolationException ex) {
              throw new BeneficiarioYaExistenteException("El Beneficiario: "+beneficiario +"; existe");
        } finally{
            daobene.cerrarDAO();
        }
    }
    public void modificarUsuario(Usuario usuario) throws SQLException, UsuarioYaExistenteException, UsuarioNoExistenteException {
            DAOUsuario daou = factoriadaos.crearDAOUsuario();
            try {
                int result= daou.update(usuario);
                if(result==0)
                    throw new UsuarioNoExistenteException("El Usuario: "+ usuario +"; no existe");
            } catch (MySQLIntegrityConstraintViolationException ex) {
                  throw new UsuarioYaExistenteException("El Usuario: "+usuario +"; existe");
            } finally{
                daou.cerrarDAO();
            }

        }
    public void actualizar(Medico medico) throws SQLException, MedicoYaExistenteException, UsuarioNoExistenteException {
        DAOMedico daomed= factoriadaos.crearDAOMedico();
        try {
            //En primer lugar se actualiza el usuario si se puede
            this.modificarUsuario((Usuario) medico);
            //Si hay error, la excepcion va hacia arriba
        } catch (UsuarioYaExistenteException ex) {
            throw new MedicoYaExistenteException(ex.toString());
        }
       //Si hay error, la excepcion va hacia arriba

       daomed.update(medico);
       daomed.cerrarDAO();
    }

    



    /*Obtencion de datos asincrono
     Usuarios, beneficiarios, Centros, medicos, horarios
     * Devuelve todos de todos
     */
    public ArrayList<Object> getUsuarios() throws SQLException {
        ArrayList<Object> usuarios= null;
        DAOUsuario daousuario= factoriadaos.crearDAOUsuario();
        usuarios= daousuario.select("SELECT * FROM Usuario");
        daousuario.cerrarDAO();
        return usuarios;
    }
    public ArrayList<Object> getBeneficiarios() throws SQLException {
        ArrayList<Object> beneficiarios= null;
        DAOBeneficiario daobene= factoriadaos.crearDAOBeneficiario();
        beneficiarios= daobene.select("SELECT * FROM Beneficiario");
        daobene.cerrarDAO();
        return beneficiarios;
    }
    public ArrayList<Object> getCentros() throws SQLException {
        ArrayList<Object> centros= null;
        DAOCentro daocentro= factoriadaos.crearDAOCentro();
        centros= daocentro.select("Select * from Centro");
        daocentro.cerrarDAO();
        return centros;
    }
    public ArrayList<Object> getMedicos() throws SQLException{
        return factoriadaos.crearDAOMedico().select("SELECT * FROM Medico");
    }
    public ArrayList<Object> getHorarios(Medico medico) throws SQLException {
        ArrayList<Object> listahoras;
        DAOHora daoHora= factoriadaos.crearDAOHora();
        listahoras= daoHora.select("SELECT * FROM Horario WHERE id_Medico_fk="+medico.getIdMedico_pk());
        daoHora.cerrarDAO();
        return listahoras;
    }
    /***************************************************************/
    /***************************************************************/



    public void eliminarusuario(Usuario usuario_aux) throws SQLException, UsuarioNoExistenteException {
        DAOUsuario daou = factoriadaos.crearDAOUsuario();
        if(daou.delete(usuario_aux) ==0){
            throw new UsuarioNoExistenteException("Usuario: " +usuario_aux +"\nNo existente");
        }
        daou.cerrarDAO();
    }
    public void eliminarmedico(Medico medico) throws SQLException {
        DAOMedico daom= new DAOMedicoMySQL();
        daom.delete(medico);
        daom.cerrarDAO();
    }
    public void eliminarbeneficiario(Beneficiario beneficiario) throws SQLException, BeneficiarioNoExistenteException {
        DAOBeneficiario daobene= factoriadaos.crearDAOBeneficiario();
        if(daobene.delete(beneficiario)== 0){
            daobene.cerrarDAO();
            throw new BeneficiarioNoExistenteException("El beneficiario: "+ beneficiario+ "No existe");
        }
        daobene.cerrarDAO();
}



    public void formatearhorario(Medico medico) throws SQLException {
        ArrayList<Object> listahoras= this.getHorarios(medico);
        DAOHora daoHora= factoriadaos.crearDAOHora();
        for(Object hora: listahoras){
            daoHora.delete(hora);
        }
        daoHora.cerrarDAO();
    }

    public Cita pedirCita(Beneficiario beneficiario, String idMedico, String FechayHora) throws SQLException, CitaYaExistenteException, BeneficiarioInexistenteException, MedicoInexistenteException, FechaNoValidaException {
        DAOMedico daom= factoriadaos.crearDAOMedico();
        DAOCita daoc= factoriadaos.crearDAOCita();
        DAOHora daoh= factoriadaos.crearDAOHora();
        DAOBeneficiario daoB= factoriadaos.crearDAOBeneficiario();

        Cita cita=null;


        Beneficiario bene= (Beneficiario) daoB.find("SELECT * FROM Beneficiario where idBeneficiario_pk= '"+beneficiario.getIdBeneficiario_pk()+"'");
        daoB.cerrarDAO();
        if(bene==null)
            throw new BeneficiarioInexistenteException("El beneficiario ya no existe");
                Medico medicoi= (Medico) daom.find("SELECT * From Medico WHERE idMedico_pk= '"+ idMedico+"'");
        daom.cerrarDAO();

        Hora hora= (Hora) daoh.find("SELECT * FROM Horario WHERE Fecha_trabajo= '"+ FechayHora +"'");
        daoh.cerrarDAO();
        if(hora==null)
            throw new FechaNoValidaException("La fecha introducida no es correcta");
        if(medicoi==null)
            throw new MedicoInexistenteException("El medico con idMedico "+ idMedico + "No existe");


         cita= new Cita(bene, medicoi, FechayHora);



        try{
            daoc.insert(cita);
         } catch (MySQLIntegrityConstraintViolationException ex) {
              throw new CitaYaExistenteException("La cita ya existe");
         }finally{
             daoc.cerrarDAO();
         }
        return cita;

    }

    public Vector<Cita> getCitas(String dni) throws SQLException {
        DAOCita daoc= factoriadaos.crearDAOCita();
        Vector<Cita> vector_citas= new Vector<Cita>();
        ArrayList<Object> listacitas= daoc.select("SELECT * FROM Cita,Beneficiario WHERE idBeneficiario_fk= idBeneficiario_pk and Nif='"+dni+"'");

        for(Object cita: listacitas){
            vector_citas.add((Cita)cita);
        }
        daoc.cerrarDAO();
        return vector_citas;
    }

    public void eliminarcitas(Cita cita) throws SQLException, CitaNoValidaException {
        DAOCita daocita= factoriadaos.crearDAOCita();
        int result= 0;
        result= daocita.delete(cita);
        daocita.cerrarDAO();
        if(result== 0)
            throw new CitaNoValidaException("No se puede eliminar la cita: "+ cita.getIdCita_pk());

    }


    public void obtenercitasmedico(String fecha) throws SQLException {
        DAOCita dAOCita= factoriadaos.crearDAOCita();
   //     ArrayList<Object> listacitas= daoc.select("SELECT * FROM Cita,Beneficiario,Medico WHERE idMedico_fk= idBeneficiario_pk and Cita.idMedico_fk= Medico.idMedico_pk and MedicoNif='"+dni+"'");
        throw new UnsupportedOperationException("Not yet implemented");
    }
    

    



    
}
